package com.dms.modules.message.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.dms.common.exception.BusinessException;
import com.dms.modules.message.dto.ChatMessageDTO;
import com.dms.modules.message.dto.MessageDetailDTO;
import com.dms.modules.message.entity.ChatMessage;
import com.dms.modules.message.mapper.ChatMessageMapper;
import com.dms.modules.message.service.ChatService;
import com.dms.modules.message.websocket.MessageWebSocket;
import com.dms.modules.user.service.UserCenterService;
import com.dms.modules.user.vo.UserInfoVO;
import com.dms.modules.message.vo.ChatContactVO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Slf4j
@Service
public class ChatServiceImpl extends ServiceImpl<ChatMessageMapper, ChatMessage> implements ChatService {

    @Autowired
    private MessageWebSocket messageWebSocket;

    @Autowired
    private UserCenterService userCenterService;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Long sendMessage(Long senderId, ChatMessageDTO messageDTO) {
        try {
            // 1. 创建消息实体
            ChatMessage message = new ChatMessage();
            message.setSenderId(senderId);
            message.setReceiverId(messageDTO.getReceiverId());
            message.setContent(messageDTO.getContent());
            message.setType(messageDTO.getType());
            message.setStatus(0); // 未读
            message.setCreateTime(LocalDateTime.now());
            
            // 2. 保存消息
            save(message);
            
            // 3. 发送WebSocket消息
            MessageDetailDTO detailDTO = new MessageDetailDTO();
            detailDTO.setId(message.getId());
            detailDTO.setType(4); // 私聊消息类型
            detailDTO.setTitle("新私信");
            detailDTO.setContent(message.getContent());
            detailDTO.setUserId(message.getReceiverId());
            messageWebSocket.sendMessage(message.getReceiverId(), detailDTO);
            
            return message.getId();
        } catch (Exception e) {
            log.error("发送私聊消息失败: senderId={}, receiverId={}, error={}", 
                    senderId, messageDTO.getReceiverId(), e.getMessage(), e);
            throw new BusinessException("发送消息失败");
        }
    }

    @Override
    public IPage<ChatMessage> getChatHistory(Long userId, Long targetUserId, Page<ChatMessage> page) {
        try {
            // 构建查询条件：(发送者=userId AND 接收者=targetUserId) OR (发送者=targetUserId AND 接收者=userId)
            LambdaQueryWrapper<ChatMessage> wrapper = new LambdaQueryWrapper<>();
            wrapper.and(w -> w
                    .and(i -> i
                            .eq(ChatMessage::getSenderId, userId)
                            .eq(ChatMessage::getReceiverId, targetUserId))
                    .or(i -> i
                            .eq(ChatMessage::getSenderId, targetUserId)
                            .eq(ChatMessage::getReceiverId, userId)))
                    .orderByDesc(ChatMessage::getCreateTime);
            
            return page(page, wrapper);
        } catch (Exception e) {
            log.error("获取聊天记录失败: userId={}, targetUserId={}, error={}", 
                    userId, targetUserId, e.getMessage(), e);
            throw new BusinessException("获取聊天记录失败");
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void markAsRead(Long receiverId, Long senderId) {
        try {
            baseMapper.markAsRead(receiverId, senderId);
        } catch (Exception e) {
            log.error("标记消息已读失败: receiverId={}, senderId={}, error={}", 
                    receiverId, senderId, e.getMessage(), e);
            throw new BusinessException("标记消息已读失败");
        }
    }

    @Override
    public int getUnreadCount(Long userId) {
        try {
            return baseMapper.getUnreadCount(userId);
        } catch (Exception e) {
            log.error("获取未读消息数失败: userId={}, error={}", userId, e.getMessage(), e);
            throw new BusinessException("获取未读消息数失败");
        }
    }

    @Override
    public IPage<ChatContactVO> getChatContacts(Long userId, Page<ChatContactVO> page) {
        try {
            // 1. 获取与当前用户有过聊天的所有用户ID
            List<Map<String, Object>> contactsWithTime = baseMapper.getContactIds(userId);
            if (contactsWithTime.isEmpty()) {
                return new Page<>(page.getCurrent(), page.getSize(), 0);
            }

            // 2. 分页获取聊天对象信息
            int start = (int) ((page.getCurrent() - 1) * page.getSize());
            int end = Math.min(start + (int) page.getSize(), contactsWithTime.size());
            List<Map<String, Object>> pageContacts = contactsWithTime.subList(start, end);

            // 3. 获取每个聊天对象的详细信息
            List<ChatContactVO> contacts = pageContacts.stream().map(contactMap -> {
                Long contactId = ((Number) contactMap.get("other_user_id")).longValue();
                LocalDateTime lastTime = (LocalDateTime) contactMap.get("last_time");
                
                ChatContactVO contact = new ChatContactVO();
                contact.setUserId(contactId);
                contact.setLastMessageTime(lastTime);

                // 获取用户基本信息
                try {
                    UserInfoVO userInfo = userCenterService.getUserInfo(contactId);
                    if (userInfo != null) {
                        contact.setNickname(userInfo.getNickname());
                        contact.setAvatar(userInfo.getAvatar());
                    } else {
                        contact.setNickname("用户" + contactId);
                        contact.setAvatar("/static/images/default-avatar.jpg");
                    }
                } catch (Exception e) {
                    log.warn("获取用户信息失败: userId={}, error={}", contactId, e.getMessage());
                    contact.setNickname("用户" + contactId);
                    contact.setAvatar("/static/images/default-avatar.jpg");
                }

                // 获取最新一条消息
                ChatMessage lastMessage = baseMapper.getLastMessage(userId, contactId);
                if (lastMessage != null) {
                    contact.setLastMessageId(lastMessage.getId());
                    contact.setLastMessage(lastMessage.getContent());
                    contact.setLastMessageType(lastMessage.getType());
                }

                // 获取未读消息数
                int unreadCount = baseMapper.getUnreadCountFromUser(userId, contactId);
                contact.setUnreadCount(unreadCount);

                return contact;
            }).collect(Collectors.toList());

            // 4. 构建分页结果
            IPage<ChatContactVO> result = new Page<>(page.getCurrent(), page.getSize(), contactsWithTime.size());
            result.setRecords(contacts);
            return result;
        } catch (Exception e) {
            log.error("获取聊天对象列表失败: userId={}, error={}", userId, e.getMessage(), e);
            throw new RuntimeException("获取聊天对象列表失败", e);
        }
    }
} 